home *** CD-ROM | disk | FTP | other *** search
- /* C-compiler utilities for types and variables storage layout
- Copyright (C) 1987, 1988 Free Software Foundation, Inc.
- Copyright (C) 1989, 1990 Apple Computer, Inc.
-
- This file is part of GNU CC.
-
- GNU CC is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 1, or (at your option)
- any later version.
-
- GNU CC is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with GNU CC; see the file COPYING. If not, write to
- the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
-
-
- #include "config.h"
- #include <stdio.h>
-
- #include "tree.h"
- #include "rtl.h" /* For GET_MODE_SIZE */
-
- #define MAX(x,y) ((x) > (y) ? (x) : (y))
- #define MIN(x,y) ((x) < (y) ? (x) : (y))
- #define CEIL(x,y) (((x) + (y) - 1) / (y))
-
- /* Data type for the expressions representing sizes of data types.
- It is the first integer type laid out.
- In C, this is int. */
-
- tree sizetype;
-
- /* An integer constant with value 0 whose type is sizetype. */
-
- tree size_zero_node;
-
- /* An integer constant with value 1 whose type is sizetype. */
-
- tree size_one_node;
-
- #define GET_MODE_ALIGNMENT(MODE) \
- MIN (BIGGEST_ALIGNMENT, \
- MAX (1, (GET_MODE_UNIT_SIZE (MODE) * BITS_PER_UNIT)))
-
- /* Chain of all permanent types we have allocated since last
- call to get_permanent_types. */
-
- tree permanent_type_chain;
-
- /* Chain of all temporary types we have allocated in this function. */
-
- tree temporary_type_chain;
-
- /* When the chains is not null, these point at the last
- types on the two chains. These help us tell whether a type
- is already on a chain. */
- tree permanent_type_end;
- tree temporary_type_end;
-
- void init_store_layout()
- {
- sizetype = 0;
- size_zero_node = 0;
- size_one_node = 0;
- permanent_type_chain = 0;
- temporary_type_chain = 0;
- permanent_type_end = 0;
- temporary_type_end = 0;
- }
-
- /* Put the newly-made type T
- on either permanent_type_chain or temporary_type_chain.
- Types that are const or volatile variants of other types
- are not put on any chain, since in the gdb symbol segment
- we do not make those distinctions.
-
- If T is already on the chain, we do nothing. */
-
- void
- chain_type (t)
- tree t;
- {
- if (TYPE_MAIN_VARIANT (t) != t)
- return;
- if (TREE_CHAIN (t) != 0)
- return;
- if (TREE_PERMANENT (t))
- {
- /* If T is on the chain at the end, don't chain it to itself! */
- if (t == permanent_type_end)
- return;
- /* Add T to the end of the chain. */
- if (permanent_type_chain == 0)
- permanent_type_chain = t;
- else
- TREE_CHAIN (permanent_type_end) = t;
- permanent_type_end = t;
- }
- else
- {
- if (t == temporary_type_end)
- return;
- if (temporary_type_chain == 0)
- temporary_type_chain = t;
- else
- TREE_CHAIN (temporary_type_end) = t;
- temporary_type_end = t;
- }
- }
-
- /* Get a chain of all permanent types made since this function
- was last called. */
-
- tree
- get_permanent_types ()
- {
- register tree tem = permanent_type_chain;
- permanent_type_chain = 0;
- permanent_type_end = 0;
- return tem;
- }
-
- /* Get a chain of all temporary types made since this function
- was last called. */
-
- tree
- get_temporary_types ()
- {
- register tree tem = temporary_type_chain;
- temporary_type_chain = 0;
- temporary_type_end = 0;
- return tem;
- }
-
- /* SAVE_EXPRs for sizes of types and decls, waiting to be expanded. */
-
- static tree pending_sizes;
-
- /* Nonzero means cannot safely call expand_expr now,
- so put variable sizes onto `pending_sizes' instead. */
-
- int immediate_size_expand;
-
- tree
- get_pending_sizes ()
- {
- tree chain = pending_sizes;
- pending_sizes = 0;
- return chain;
- }
-
- /* Given a size SIZE that isn't constant, return a SAVE_EXPR
- to serve as the actual size-expression for a type or decl. */
-
- static tree
- variable_size (size)
- tree size;
- {
- size = save_expr (size);
-
- if (global_bindings_p ())
- {
- error ("variable-size type declared outside of any function");
- return build_int (1);
- }
-
- if (immediate_size_expand)
- expand_expr (size, 0, VOIDmode, 0);
- else
- pending_sizes = tree_cons (0, size, pending_sizes);
-
- return size;
- }
-
- /* Return the machine mode to use for an aggregate of SIZE bits.
-
- Note!!! We only use a non-BLKmode mode if the size matches exactly.
- There used to be the idea of using